;------------------------------------------------------------------------------
; This is the 4k intro of Seb which won 2nd place at the State of the Art 2004.
;
; To make it run on other emulators and as a practise I concatenated all. You
; have to blame me for converting the source code from A22 syntax to ASxxxx
; syntax. Credit and copyright of all demo code if left to Seb, I wrote just
; the BASIC header which could have been done by any lamer.
;
; However, have a lot of fun!!
;
; Bodo Wenzel, January 2006
;------------------------------------------------------------------------------

	.module	rezurrection

	.area	CODE (abs)
	.org	0x4009

	.db	0		; VERSN
	.dw	0		; E_PPC
	.dw	dsp		; D_FILE
	.dw	dsp+1		; DF_CC
	.dw	var		; VARS
	.dw	0		; DEST
	.dw	var+1		; E_LINE
	.dw	last-1		; CH_ADD
	.dw	0		; X_PTR
	.dw	last		; STKBOT
	.dw	last		; STKEND
	.db	0		; BERG
	.dw	membot		; MEM
	.db	0		; unused
	.db	2		; DF_SZ
	.dw	0		; S_TOP
	.db	0xFF,0xFF,0xFF	; LAST_K
	.db	55		; MARGIN
	.dw	line2		; NXTLIN (Autostart)
	.dw	0		; OLDPPC
	.db	0		; FLAGX
	.dw	0		; STRLEN
	.dw	0x00C8D		; T_ADDR
	.dw	0		; SEED
	.dw	0xFFFF		; FRAMES
	.db	0,0		; COORDS
	.db	0xBC		; PR_CC
	.db	33,24		; S_POSN
	.db	0b01000000	; CDFLAG
	.ds	33		; output buffer
membot:
	.ds	30		; calculation buffer
	.ds	2		; unused

;- The first line contains the machine code ---------------------

line1:				; starts at 0x407D

	.db	0,1		; 1
	.dw	line2-0x407D-4	; length
	.db	0xEA		; REM

				; falls through to part 1

;------------------------------------------------------------------------------
;
; As yet untitled
; The Calodox 1k ZX81 Intro
; Copyright (c) 2003 Sebastian Gerlach
;
; 1. Scroller
;
; Displays a huge scrolling text with shadow.
;
;------------------------------------------------------------------------------

	ld	hl,#begin_1
	ld	de,#end_1 - begin_1 + 1
	call	mock_load

begin_1:

htop	= 17
hbot	= 8

;	ld sp, 0x42fe
	ld ix, #traceproc_1
	out (0xfe), a

	.if	0
	ld hl, #buffer43	; 0x4300
	ld (hl), #0
	ld de, #buffer43 + 1	; 0x4301
	ld bc, #255
	ldir
	.endif

loop_around_1:
modhere2:
	ld b, #2
waiter_1:
	ld hl, #lflag_1
	ld (hl), #0
tag_1:
	bit 0, (hl)
	jr z, tag_1

	ld hl, #drawproc_1
	ld a, #0xeb
	xor (hl)
modhere:
	ld (hl), a

	djnz waiter_1

	ld a, (tcharoff)	; Load current bit offset
	or a			; Check if zero
	jr nz, charvalid	; If non zero, we still have some columns left

	; Reload a new character from ROM...

	ld hl, #charcnt
	dec (hl)
	jr nz, keepup
	xor a
	ld (modhere), a
	inc a
	ld (modhere2+1), a
keepup:
	inc l
	dec (hl)
	jr nz, keepup2
	ld a, #0x28
	ld (modns1), a
	ld a, #71
	ld (modns2+1), a
keepup2:

	ld hl, (stroff)		; hl points to next char in string
	ld a, (hl)		; load char into a
	inc hl			; increment string pointer
	ld (stroff), hl		; store it again

	scf
	ld bc, #stringend
	sbc hl, bc
	jp z, end_1

	; a now contains char
	; Compute character offset in hl
	; We want hl=1e01h+8*a
	; a is between 00h and 3fh -> hl is between 1e01 and 1ff9h

	ld h, #0x0f		; Will be 1e or 1f later
	rlca			; Rotate and clear carry (MSB is always 0)
	rla			; Rotate through carry
	rla			; Rotate through carry (highest bit of char is now in carry
	rl h			; Shift in carry to h (h is now 1e or 1f)
	ld l, a			; Keep rest in l
	inc l			; Skip first line of char

	ld de, #tchar		; Load temp char address

	ld b, #6		; Copy 6 lines of character
loadcharline_1:
	ld a, (hl)		; 7 Load line
	ld c, a			; 4 Copy line
	rrca			; 4 Shift original line
	or c			; 4 Or them together (thickens char)
	ld (de), a		; 7 Store result
	inc e			; 4 Increment de
	inc l			; 4 Increment hl
	djnz loadcharline_1	; 13 Load next line

;	ld bc, #6		; 10 Copy 6 lines
;	ldir			; 21 Do the copy
	ld a, #8		; Set the remaining bit counter to 8
	ld (de), a		; Store it

charvalid:
	ld hl, #tchar		; Address of temporary char
	ld b, #6		; Number of lines to copy
	ld de, #buffer43 + 8	; 0x4308	; Address of framebuffer
nextcharline:
	push bc
	push hl
	ld h, d			; Prepare for copy
	ld l, e
	inc l			; Source is one byte further (we scroll to the left...)
	ld bc, #39		; Shift over 31 chars
	ldir			; Copy them
	pop hl			; Get back temp char address

	xor a			; Clear a
	rlc (hl)		; Get bit into carry
	sbc a, #0		; Substract carry once (carry unchanged)
	sbc a, #0		; And again, now a is 0 or feh
	ld (de), a		; Load into frame buffer
	inc e			; Increment frame buffer pointer

	inc l			; Move onto next char line

	pop bc
	djnz nextcharline	; Continue until 6 lines out

	dec (hl)		; Decrement remaining bit count

	jp loop_around_1

tchar:		.db 0,0,0,0,0,0
tcharoff:	.db 0
stroff:		.dw string
charcnt:	.db 105		; Until speedup
charcnt2:	.db 60		; Until shadow

lflag_1:	.db 0

drawproc_1:	ld r, a		; 0edh 04fh / 006h 04fh
	ld b, #6
hr_1:	djnz hr_1
	ld b, #htop
	ld c, #6
	ld ix, #endofline_1
	ld a, #buffer43_highbyte	; 0x43
	ld i, a
;	xor a
	ld a, #8

	; We have 50 frames per second
	; 314 scanlines per frame
	; 207 clocks per scanline
	; In all, 3249900 clocks per second
	; This is close enough to 3.25 MHz

nextline_1:	jp oneline_1+0x8000		; 10
oneline_1:	ld r,a				; 9
	.db 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0	; 64  16x4
	.db 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0	; 64  16x4
	.db 0,0,0,0,0,0,0,0
	jp (ix)					; 8
endofline_1:					; = 155

mod1:				; Modify for skewed mirrored text
	add a,#0		; Either add 0 (7) or nop nop (8)
	djnz nextline_1		; 13,8

				; = 202

	ld b, #13		; 7
lp:	djnz lp			; 13, 8
mod2:
	ld b, #htop 		; 7 Character height (either htop or hbot)

	nop			; 4w
	ld d,(hl)		; 7w
mod3:
	add a, #40		; 7 Vidmem delta (+40 or -40)
	dec c			; 4
	jr nz, nextline_1	; 12,7		; 30

	ld b, #8		; 7
lp2:	djnz lp2		; 13, 8
	ld hl, #mod2+1
	ld a, #hbot
	cp (hl)
modns1:
	jr finished		; originally 18h, then 28h (jr/jr z)
	ld (hl), a
	ld b, a
	ld a, #0
	ld (mod1), a
	ld a, #-40
	ld (mod3+1), a
	ld a, #-48
	ld c, #6
	jr nextline_1

finished:

	ld a, #htop
	ld (mod2+1), a
	ld a, #40
	ld (mod3+1), a
	ld a, #0xc6
	ld (mod1), a
	ld ix, #traceproc_1
modns2:
	ld a, #126		; originally 140, then 71
	ld hl, #lflag_1
	ld (hl), #1		; Allow main loop to run
	jr doret_1

traceproc_1:
	in a, (0xfe)
	ld b, #80
here_1:	djnz here_1

	ld ix, #drawproc_1
	out (0xff),a
	ld a, #71
doret_1:
	jp 0x029e

string:
	.db 0x17,0x17,0x17,0x00,0x28,0x26,0x31,0x34	; "*** CALO"
	.db 0x29,0x34,0x3d,0x00,0x35,0x37,0x2a,0x38	; "DOX PRES"
	.db 0x2a,0x33,0x39,0x38,0x00,0x26,0x00,0x20	; "ENTS A 4"
	.db 0x30,0x00,0x2e,0x33,0x39,0x37,0x34,0x00	; "K INTRO "
	.db 0x2b,0x34,0x37,0x00,0x38,0x2e,0x33,0x28	; "FOR SINC"
	.db 0x31,0x26,0x2e,0x37,0x00,0x3f,0x3d,0x24	; "LAIR ZX8"
	.db 0x1d,0x00,0x17,0x17,0x17,0x00,0x00,0x00	; "1 ***   "
	.db 0x00,0x00,0x00,0x15,0x15,0x00,0x2c,0x37	; "   ++ GR"
	.db 0x2a,0x2a,0x39,0x38,0x00,0x39,0x34,0x00	; "EETS TO "
	.db 0x3e,0x3b,0x2a,0x38,0x00,0x26,0x33,0x29	; "YVES AND"
	.db 0x00,0x26,0x31,0x31,0x00,0x34,0x3a,0x37	; " ALL OUR"
	.db 0x00,0x2b,0x37,0x2e,0x2a,0x33,0x29,0x38	; " FRIENDS"
	.db 0x00,0x15,0x15,0x00,0x00,0x00,0x00,0x00	; " ++     "
	.db 0x2c,0x2a,0x39,0x00,0x37,0x2a,0x26,0x29	; "GET READ"
	.db 0x3e,0x00,0x2b,0x34,0x37,0x00,0x31,0x34	; "Y FOR LO"
	.db 0x26,0x29,0x2e,0x33,0x2c,0x00,0x33,0x2a	; "ADING NE"
	.db 0x3d,0x39,0x00,0x35,0x26,0x37,0x39,0x00	; "XT PART "
	.db 0x16,0x00,0x3e,0x2a,0x26,0x2d,0x1a,0x00	; "- YEAH, "
	.db 0x3c,0x2a,0x00,0x2d,0x26,0x3b,0x2a,0x00	; "WE HAVE "
	.db 0x34,0x33,0x31,0x3e,0x00,0x1d,0x30,0x00	; "ONLY 1K "
	.db 0x34,0x2b,0x00,0x37,0x26,0x32,0x00,0x0e	; "OF RAM :"
	.db 0x16,0x11					; "-)"

	.db 0,0,0,0,0,0,0,0,0
stringend:

end_1:				; falls through to part 2

;------------------------------------------------------------------------------
;
; As yet untitled
; The Calodox 1k ZX81 Intro
; Copyright (c) 2003 Sebastian Gerlach
;
; 2. Copper
;
; Displays traditional copper bars.
;
; Copper bar by Fred
;
;------------------------------------------------------------------------------

	ld	hl,#begin_2
	ld	de,#end_2 - begin_2 + 1
	call	mock_load

	ld hl,#bar
	ld de,#buffer42
	ld bc,#256
	ldir

begin_2:

	COUNT =  8

	ld ix, #traceproc_2
;	ld sp, 0x43fe
	out (0xfe), a

loop_around_2:
	ld hl, #lflag_2
	ld (hl), #0
tag_2:
	bit 0, (hl)
	jr z, tag_2

	ld hl, (frames_2)
	inc hl
	ld (frames_2), hl

	ld a, h
	or a
	jr nz, docoppers

	bit 7, l
	ld a, #0x11
	jr z, bgl1
	ld a, #0x44
bgl1:
	call zstuff
	jr loop_around_2

docoppers:
	ld d, l

	cp #11
	jr c, nospec
	cp #13
	jr nc, killcop
	xor a
	call zstuff
	jr nospec
killcop:
	cp #15
	jp nc, end_2		; was jr
	xor a
	ld h, #buffer42_highbyte	; 0x42
	ld (hl), a
nospec:
	ld iy, #coppers

	ld e, #COUNT
c_next:
	xor a
	ld (cdist), a
	ld a, (frames_2+1)
	cp e
	jr z, c_come
	jr nc, c_keep
	ld a, #255
	jr s_final
c_come:
	ld a, #255
	sub d
	ld (cdist), a
c_keep:
	ld a, #COUNT
	sub e
	rlca
	rlca
	rlca
	rlca
	add d

	; Get sine of a
	ld hl, #sine_2
	ld c, a
	bit 6, c
	jr z, s_noflip_2
	cpl
s_noflip_2:
	and #0x3f
	add l
	ld l, a
	ld a, (hl)
	; a contains sine

	bit 7, c
	jr nz, s_done_2
	neg
s_done_2:
	add #92
	ld b, a
	ld a, (cdist)
	add b
	jr nc, s_final
	ld a, #255
s_final:
	cp #180
	jr c, s_keep
	ld a, #255
s_keep:
	ld 0(iy), a
	inc iy
	dec e
	jr nz, c_next

	;
	; Now sort the coppers
	;

	ld bc, #coppers
	ld hl, #coppers+1
	ld e, #COUNT
lo2:
	ld a, (bc)
	push bc
	ld d, e
lo1:
	cp (hl)
	jr c, sm
	ld a, (hl)
	pop iy
	push hl
sm:	inc hl
	dec d
	jr nz, lo1
	pop hl
	ld d, (hl)
	ld a, (bc)
	ld (hl), a
	ld a, d
	ld (bc), a

	inc bc
	push bc
	pop hl
	inc hl
	dec e
	jr nz, lo2

	;
	; Generate command set
	;
	ld hl, #coppers
	ld iy, #commands
	ld e, #COUNT
	ld a, (hl)
	jr gstrt
gcl:
	ld b, (hl)
	inc l
	ld a, (hl)
	sub a, #2
	cp b
	jr z, gforget ; Don't even try
	jr c, gforget ; Don't even try

	cp (iy)
	jr c, gov
	jr z, gov
	inc iy
	inc iy
gov:
	add a, #2
gstrt:

	ld (iy), a
	ld 1(iy), #0
	add a, #9
	ld 2(iy), a
	ld 3(iy), #2
	bit 0, a
	jr nz, gbok
	set 5, 3(iy)
gbok:
	inc iy
	inc iy
gforget:
	dec e
	jr nz, gcl

	inc iy
	inc iy

	ld (iy), #0xff

	ld iy, #commands
	ld b, (iy)
cdl:
	ld a, 2(iy)
	cp a, #0xff
	jr z, cdone
	ld c, a
	sub b
	dec a
	ld 2(iy), a
	ld b, c
	inc iy
	inc iy
	jp cdl
cdone:

	jp loop_around_2

zstuff:
	ld h, #buffer43_highbyte	; 0x43
	srl l
	srl l
	ld (hl), a
	ret

lflag_2:	.db 0
frames_2:	.dw 000
cdist:		.db 240

drawproc_2:	ld b, #6
hr_2:	djnz hr_2
	nop
	ld hl, #modaddr
	ld b, #192
	ld ix, #endofline_2
	ld hl, #commands
	ld d, (hl)
	ld a, #buffer43_highbyte	; 0x43
	ld i, a
	xor a

	; We have 50 frames per second
	; 314 scanlines per frame
	; (294 visible lines, and 20 retrace lines)
	; The above numbers are estimated, I should check them.
	; 207 clocks per scanline
	; In all, 3249900 clocks per second
	; This is close enough to 3.25 MHz

nextline_2:	jp oneline_2+0x8000		; 10
oneline_2:	ld r,a				; 9
	.db 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0	; 64  16x4
	.db 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0	; 64  16x4
	jp (ix)					; 8
endofline_2:					; = 155
	dec d			; 4
	jr z, actcopper		; 7,12
	add a, #32		; 7
modaddr:
	res 6, a		; either nop,nop (00000h) or res 6,a (0b7cbh)

	ld r, a			; 9w
	nop			; 4w
goon:				; = 194
	djnz nextline_2		; 13
	ld hl, #lflag_2
	ld (hl), #1		; Allow main loop to run
	ld ix, #traceproc_2
	jr doret_2

actcopper:			; 171 cycles in
	dec b			; 4
	inc hl			; 6
	ld e, (hl)		; 7
	srl e			; 8 carry now indicates whether we want extra blank
	srl e			; 8 carry now indicates operation
	ld a, #buffer42_highbyte	; 0x42	; 7 = 44

	jr nc, mbg		; 7,12

	inc a			; 4
	ld iy, #0xb7cb		; 14!
	jr mdo			; 12 = 37
mbg:
	ld iy, #0		; 14!
	nop			; 4
	ld d,(hl)		; 7 = 37
mdo:
	ld (modaddr), iy	; 20
	ld i, a			; 9
	sla e			; 8
	sla e			; 8
	ld a, e			; 4 = 307

	inc hl			; 6
	ld d, (hl)		; 7

	add iy,iy		; 15w
	nop			; 4w

	exx			; 4
	ld b, #4		; 7
w0:	djnz w0			; 13,8
	exx			; 4   23+7*13
	jp goon			; 10

traceproc_2:
	in a, (0xfe)
	ld b, #80
here_2:	djnz here_2

	ld ix, #drawproc_2
	out (0xff),a
doret_2:
	ld a, #55
	jp 0x029e

bar:

;-------------------------------------------------
; Copper bar by fred
;-------------------------------------------------

	; "CALODOX" with black border
	.db 255,255,255,255,255,255,255,255
	.db 255,255,255,255,255,255,255,255
	.db 255,255,255,255,255,255,255,255
	.db 255,255,255,255,255,255,255,255
	.db 192,  0,  0,  0,  7,  0,  0,  0
	.db   0,252,  0,  7,255,255,128,  0
	.db   0,  0, 56,  0,  0,  0,  1,224
	.db   0,  0,  0, 14,  0,  7,  0,  1
	.db 128,  0,124,  0,  6,  0, 15,240
	.db   0,120,  0, 15,255,255,  0,  0
	.db 192,  0, 56,  0,124,  0,  0,224
	.db   0, 24,  0,  7,  0,  0,  0,  3
	.db 128,  3,255,255,254,  0,  0,  0
	.db   0,120,  0, 15,255,255,  0,  1
	.db 224,  0, 24,  0,126,  0,  0,192
	.db   0, 60,  0,  7,128,  0,  0,  7
	.db 128,  3,255,255,252,  0,  0,  0
	.db   0, 48,  0,  0,  0,  2,  0,  1
	.db 224,  0, 24,  0,126,  0,  0,192
	.db   0, 60,  0,  3,192,  0,  0, 15
	.db 128,  0,124,  0,  4,  0, 63,252
	.db   0, 48,  0,  0,  0,  6,  0,  0
	.db 192,  0, 24,  0,124,  0,  0,192
	.db   0, 24,  0,  3,128,  0,  0,  7
	.db 192,  0,  0,  0,  4,  0,127,254
	.db   0, 48,  0,  0,  0,  6,  0,  0
	.db   0,  0, 56,  0,  0,  0,  1,224
	.db   0,  0,  0,  3,  0,  7,  0,  3
	.db 255,255,255,255,255,255,255,255
	.db 255,255,255,255,255,255,255,255
	.db 255,255,255,255,255,255,255,255
	.db 255,255,255,255,255,255,255,255

	.if	0	;.comment white
	; "CALODOX" with white border
	.db 192,  0,  0,  0, 31,  0,  0,  0
	.db   3,252,  0,  7,255,255,192,  0
	.db   0,  1,240,  0,  0,  0,  7,240
	.db   0,  0,  0,124,  0, 31,  0,  3
	.db 128,  0,  0,  0, 14,  0,  0,  0
	.db   1,248,  0, 15,255,255,  0,  0
	.db   0,  0,112,  0,  0,  0,  3,192
	.db   0,  0,  0, 28,  0, 14,  0,  3
	.db   0,  0,248,  0, 12,  0, 31,224
	.db   0,240,  0, 31,255,254,  0,  1
	.db 128,  0,112,  0,248,  0,  1,192
	.db   0, 48,  0, 14,  0,  0,  0,  7
	.db   0,  7,255,255,252,  0,  0,  0
	.db   0,240,  0, 31,255,254,  0,  3
	.db 192,  0, 48,  0,252,  0,  1,128
	.db   0,120,  0, 15,  0,  0,  0, 15
	.db   0,  7,255,255,248,  0,  0,  0
	.db   0, 96,  0,  0,  0,  4,  0,  3
	.db 192,  0, 48,  0,252,  0,  1,128
	.db   0,120,  0,  7,128,  0,  0, 31
	.db   0,  0,248,  0,  8,  0,127,248
	.db   0, 96,  0,  0,  0, 12,  0,  1
	.db 128,  0, 48,  0,248,  0,  1,128
	.db   0, 48,  0,  7,  0,  0,  0, 15
	.db 128,  0,  0,  0,  8,  0,255,252
	.db   0, 96,  0,  0,  0, 12,  0,  0
	.db   0,  0,112,  0,  0,  0,  3,192
	.db   0,  0,  0,  6,  0, 14,  0,  7
	.db 192,  0,  0,  0, 24,  0,255,252
	.db   0, 96,  0,  0,  0, 30,  0,  0
	.db   0,  0,240,  0,  0,  0,  7,224
	.db   0,  0,  0, 14,  0, 31,  0,  7
	.endif		;.comment white
	.if	0	;.comment oldbmp
	; "CDX" on a black bar
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0x00,0x00,0xff
	.db 0x00,0x00,0xff,0xff,0x00,0xff,0x00,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0x00,0x00,0x00,0xff
	.db 0x00,0x00,0x00,0xff,0x00,0xff,0x00,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0x00,0xff,0xff,0xff
	.db 0x00,0xff,0x00,0xff,0xff,0x00,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0x00,0xff,0xff,0xff
	.db 0x00,0xff,0x00,0xff,0xff,0x00,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0x00,0x00,0x00,0xff
	.db 0x00,0x00,0x00,0xff,0x00,0xff,0x00,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0x00,0x00,0xff
	.db 0x00,0x00,0xff,0xff,0x00,0xff,0x00,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.db 0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff
	.endif		;.comment oldbmp

	; At 4300h, length 20h
bg:
;	.ds 64

	.if	0	;.comment setbg
	.db 0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11
	.db 0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11
	.db 0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11
	.db 0x11,0x11,0x11,0x11,0x11,0x11,0x11,0x11
	.db 0x44,0x44,0x44,0x44,0x44,0x44,0x44,0x44
	.db 0x44,0x44,0x44,0x44,0x44,0x44,0x44,0x44
	.db 0x44,0x44,0x44,0x44,0x44,0x44,0x44,0x44
	.db 0x44,0x44,0x44,0x44,0x44,0x44,0x44,0x44
	.endif		;.comment setbg

sine_2:
	.db  0, 2, 4, 6, 8,10,12,14
	.db 16,18,20,22,23,25,26,28
	.db 30,32,34,35,37,39,41,42
	.db 44,46,47,49,50,52,53,55
	.db 56,57,59,60,61,63,64,65
	.db 66,67,68,69,70,71,72,73
	.db 73,74,75,75,76,77,77,78
	.db 78,78,79,79,79,79,79,79

memend	= buffer43 + 128	; memend:
coppers = memend
commands = coppers+COUNT+1
	; command can be:
	; xxx00000 - start copper at line xxx
	; xxx00010 - start background at line xxx
	; Set bit 0 for an additional blank line
	; All commands start with a blank line
	; delta command

end_2:				; falls through to part 3

;------------------------------------------------------------------------------
;
; As yet untitled
; The Calodox 1k ZX81 Intro
; Copyright (c) 2003 Sebastian Gerlach
;
; 3. Skyscroller
;
; Presents a scrolling starfield with text fade-in/fade-out.
;
; ThreeHeads logo by Fred
;
;------------------------------------------------------------------------------

	ld	hl,#begin_3
	ld	de,#end_3 - begin_3 + 1
	call	mock_load

	ld hl,#oneline3 + 2
	ld de,#buffer42
	ld bc,#256
	ldir

	ld hl,#logo
	ld de,#buffer43
	ld bc,#120
	ldir

begin_3:

	starcount =  76

; Code starts at 4034h

	ld ix, #traceproc_3
;	ld sp, 0x43fe

	ld hl, #fontmem		; Initialize star positions
	ld de, #fontmem+1
	ld (hl), #0
	ld bc, #111
	ldir

	out (0xfe), a

loop_around_3:

	ld hl, #lflag_3
	xor a
	ld (hl), a
tag_3:
	or (hl)
	jr z, tag_3

	ld hl, #incmod		; ld l, #incmod		; h is identical to lflag
	ld a, #0x3c		; 3c = inc a / af = xor a / 93=3c^af
	xor (hl)
	ld (hl), a

	ld hl, (frames_3)
	inc hl
	ld (frames_3), hl

modfinal2:
	ld a, #1
	cp h
jmpfinal:
	jr c, normal		; change to 9ch for final
	bit 0, l
	jr nz, loop_around_3

	jr addstars		; added by BW
	jp end_3		; added by BW

;-------------------------------------------------
; addstars
; Add stars to view
;-------------------------------------------------
addstars:
	ld h, #buffer42_highbyte	; 0x42
	ld a, (spos)
	add #41
	ld (spos), a
	ld l, a

	cp #starpos+1
	jr c, loop_around_3
	cp #starpos+starcount
	jr nc, loop_around_3

	ld a, (vpos)
	add #121
;	rlca
	ld (vpos), a
	and #127
modadd:
	ld (hl), a
	or h			; is 180, since the ld (hl), a above
				; is swapped for ld (hl), imm. later
	jr loop_around_3

normal:
	ld a, #starcount
	bit 0, l
	jr z, ndisp
	ld a, (posy)
ndisp:
	ld (inneroff), a

	ld a, l
	and #3
	jr nz, noup
	ld a, (posy)
	cp #71
	jr c,good
	xor a
good:
	inc a
	ld (posy), a

	ld a, (posx)
	inc a
	cp #140
	jr c,good2
	xor a
good2:
	ld (posx), a

noup:

	ld a, (frames_3)
	and #127
	jr nz, ldone

	ld hl, (textptr)
	ld a, (hl)
	ld (posx), a
	inc hl			; inc l
	ld a, (hl)
	ld (posy), a
	inc hl			; inc l

;	ld a, (moddisproc+1)
;	xor #0x43
;	ld (moddisproc+1), a
;	heavily modified by BW
;	dodis  = 0x--b0 => po
;	dodis2 = 0x--f3 => pe
	ld bc, (moddisproc+1)
	ld de, #dodis
	ld a,c
	cp e
	ld b,d
	ld c,e
	jr nz,bodo
	ld bc, #dodis2
bodo:
	ld (moddisproc+1), bc

	ld de, #0x7400
	jr z, vload		;	jp pe, vload

	ld a,(hl)		; 	and (hl)
	and a			; 	and (hl)
	jr z, lasttext

	call loadchars
	inc hl
	ld (textptr), hl
	ld de, #0x3878

vload:
	ld (vidparm),de
	xor a
ldone:

	ld de, (vidparm)

	cp #64
	ld a, #0x6f
	jr c,flow
	ld a, #0x2e
	ld de, #0x7400
flow:
	ld (modl0),a

;-------------------------------------------------
; prepchars
; Update some character bits
; Mod: a, bc
;-------------------------------------------------
	ld b, #7			; Copy 7 bytes
nval:
	ld a, (spos)		; Current copy position
	add #37			; Add some prime number
	ld (spos), a		; Store result
	cp d			; Compare with size of buffer
	jr nc, valnok		; If larger, ignore this byte
	add e			; Add memory offset to source
	ld h, #buffer43_highbyte	; 0x43		; High byte of hl
modl0:
	ld l, a			; Low byte of hl  ; ld l,imm. (2eh) or ld l,a (6fh)
	nop			; Zero for mod prev
	ld c, (hl)		; Load source byte
	add d			; Adjust to destination
	ld l, a			; Low byte of hl
	ld (hl), c		; Store byte
valnok:
	djnz nval		; Loop until done
sloop_around:
	jp loop_around_3

lasttext:
	ld a, #10
	ld (modfinal2+1), a
	ld a, #0x36
	ld (modadd), a
	ld a, #6		;	ld a, #0x9c
	ld (jmpfinal+1), a
	jr sloop_around

;-------------------------------------------------
; loadchars
; Load a string into character memory
; Mod: a, bc
; In: hl - pointer to text
;-------------------------------------------------
loadchars:
	ld de, #fontmem		; Destination bitmap pointer
nextchar:
	ld a, (hl)		; Load char from string
	or a			; Test if zero
	ret z			; If zero, quit
	inc l			; Increment string pointer
	push hl			; Store it for future reference

	ld h, #0x0f		; Will be 1e or 1f later to access ROM char table
	rlca			; Rotate and clear carry (MSB is always 0)
	rla			; Rotate through carry
	rla			; Rotate through carry (highest bit of char is now in carry
	rl h			; Shift in carry to h (h is now 1e or 1f)
	ld l, a			; Keep rest in l
	inc l			; Skip first line of char

	ld b, #7		; Copy 7 lines of character
loadcharline_3:
	ld a, (hl)		;  7 Load line
	ld c, a			;  4 Copy line
	rrca			;  4 Shift original line
	or c			;  4 Or them together (thickens char)
	ld (de), a		;  7 Store result
	ld a, #8		;  7 Update position in de
	add e			;  4
	ld e, a			;  4
	inc l			;  4 Increment hl
	djnz loadcharline_3	; 13 Load next line
	ld a, #-55		; Move back to top of next column
	add e
	ld e, a
	pop hl			; Recover string pointer
	jr nextchar		; Loop until done

;-------------------------------------------------
; drawproc
; Render display
;-------------------------------------------------
drawproc_3:	ld hl, #starpos
	ld a, (hl)			; Delay before first line
	add #73+10-3		; add #73+10
	call delay_3
	ld a, (inneroff)
	ld b, a
continue:

	ld ix, #endofline_3
	ld a,#buffer42_highbyte	; ld a, h	; h already contains 42h
	ld i, a
nextline_3:	ld a, l
	and #3
	jp oneline_3+0x8000		; 10
oneline_3:	ld r,a			; 9
lflag_3:	.db 0			; Place lflag here, since it will never have bit 6 at one
	jp (ix)				; 8
endofline_3:
	ld a, #191
	sub (hl)
	inc l
	push af
	ld a, l
	and #3
incmod:
	inc a			;	xor a
	ld d, a
	ld a, (hl)
	cp #180			; 7
	jr z, skipdis
	sub d			; 4
	jr nc,dok_3		; 7
	add #180			; 7
	jr dol			; 12
skipdis:
	ld a, (hl)
	nop
dok_3:				; 12
	ld c,(hl)		; 7
	ld c,(hl)		; 7
dol:
	ld (hl), a
	ld c, a
	pop af
	add c
	exx
	call delay_3

	ld b, #5
blu:	djnz blu
	exx

	dec b
	jr nz, nextline_3

	ld a, #starpos+starcount
	cp l
	jr z, final

	ld a, #180
	sub (hl)
	ld b, a
	ld a, (posx)
	add b
	call delay_3

	ld a, #buffer43_highbyte	; 0x43
	ld i, a
moddisproc:
	jp dodis		; 41b0 or 41f3

;	.ds 0x41b0-.		; To ensure address of this label
				; has an appropriate parity
dodis:
	ld c, #14
	ld a, #vidmem
	ld ix, #endofline2
nextline2:	jp oneline2+0x8000	; 10
oneline2:	ld r,a			; 9
	.db 0,0,0,0,0,0,0,0
	jp (ix)				; 8
endofline2:
	dec c
	jr z, flog
	bit 0, c
	jr nz, fog
	add #8
	jr fjd
fog:
	ld b,(hl)
	ld b,(hl)
fjd:
	ld b,(hl)			; 7w
	nop				; 4w
	ld b, #6			; 7w
dfg:	djnz dfg			; 13w

	jr nextline2			; 13
flog:

	ld a, #6
	add l
	ld l, a

dodisend:
	ld a, (posx)
	ld b, a
	ld a, #230-3		; 	ld a, #230
	sub b
	add (hl)
	call delay_3

	ld a, #starpos+starcount
	sub l
	ld b, a
	jp continue

;-------------------------------------------------
; Don't touch this value! It's parity was
; carefully studied :-)
;-------------------------------------------------
;	.ds 0x41f3-.
dodis2:
	ld c, #29
	ld a, #0x74
	ld ix, #endofline3

	jp oneline3+0x8000	; 10
oneline3:	ld r,a		; 9
;-------------------------------------------------
; Framebuffer for stars
; Must be located at 4200h
; This is achieved by carefully placing preceding
; code :-)
;-------------------------------------------------
	.db 1,3,7,15

	jp (ix)			; 8
final:
	ld hl, #lflag_3
	ld (hl), #1		; Allow main loop to run
	ld ix, #traceproc_3
	jr doret_3
endofline3:
	dec c
	jr z, flog2
	add #4
	ld b, #10		; 7w
dfg2:	djnz dfg2		; 13w
	ld b,(hl)		; 7w
	ld b,(hl)		; 7w

	jp oneline3+0x8000	; 10
flog2:
	nop
	ld a, #11
	add l
	ld l, a
	jr dodisend

traceproc_3:
	in a, (0xfe)
	ld b, #80
here_3:	djnz here_3

	ld ix, #drawproc_3
	out (0xff),a
doret_3:
	ld a, #36
	jp 0x029e

;-------------------------------------------------
; Variables part 2
;-------------------------------------------------
frames_3:	.dw 00
textptr:	.dw text
vpos:		.db 45
spos:		.db 73
inneroff:	.db starcount
posy:		.db 1
posx:		.db 2

vidparm:	.dw 0x3878

;-------------------------------------------------
; delay
; Delay for a+144 clock cycles (call: 17)
; Carry adds 256 cycles
; Mod: a, bc
;-------------------------------------------------
delay_3:
	jr nc, shortdelay
	; 5+256 to go
	nop
	nop
	nop
	ld b, #19
dsjf:	djnz dsjf
shortdelay:
	ld b, a			; 4
	and #3			; 7
	add #insts_3		; 7
	ld (modme+1), a		; 13
modme:
	ld a, (insts_3)		; 13
	ld (strt_3), a		; 13
strt_3:
	nop			; 4			61

	srl b			; 8
	srl b			; 8
	ld a, b 		; 4
	cpl			; 4
	and #3			; 7
	ld (jop_3-1), a		; 13
	jr jop_3		; 12		117
jop_3:
	nop
	nop
	nop
	srl b			; 8
	srl b			; 8
	ret z			; 11		144
	; Missing 6 cycles because ret not taken
loophere_3:
	dec b
	jr nz, loophere_3
	; Missing another 5 cycles because of last jr not taken
	ret z
	; Takes the 11 cycles we have left :-)
	; Simply ret would have been one cycle too fast for us here

insts_3:
	nop			; 4
	ret c			; 5
	inc bc			; 6
	ld a,(bc)		; 7

text = buffer42 + 0x0077		; text:
	.db 30,30
	.db 0x28,0x34,0x29,0x2a,0			; "CODE"
	.db 80,1
	.db 0x32,0x2e,0x33,0x26,0x38,0			; "MINAS"
	.db 1,10
	.db 0x2c,0x37,0x26,0x35,0x2d,0x2e,0x3d,0	; "GRAPHIX"
	.db 50,16
	.db 0x2b,0x37,0x2a,0x29,0			; "FRED"
	.db 20,25
	.db 0x32,0x3a,0x38,0x2e,0x28,0			; "MUSIC"
	.db 50,30
	.db 0x33,0x34,0x33,0x2a,0x0e,0x16,0x11,0	; "NONE:-)"
	.db 10,10,0
	.db 0
	.db 0,0,0,0,0

;-------------------------------------------------
; Star positions. First star must be invisible.
;-------------------------------------------------
starpos = buffer42 + 0x00B2		; starpos:
	.db 180,180,180,180,180,180,180,180
	.db 180,180,180,180,180,180,180,180
	.db 180,180,180,180,180,180,180,180
	.db 180,180,180,180,180,180,180,180
	.db 180,180,180,180,180,180,180,180
	.db 180,180,180,180,180,180,180,180
	.db 180,180,180,180,180,180,180,180
	.db 180,180,180,180,180,180,180,180
	.db 180,180,180,180,180,180,180,180
	.db 180,180,180,180,0

;-------------------------------------------------
; ThreeHeads logo by fred
;-------------------------------------------------
logo:
	; ThreeHeads white in black circle
	.db   0,  0,  0,  0,  0, 15,248,  0
	.db   0, 63,254,  0,  0,255,255,128
	.db   1,255,255,192,  3,255, 15,224
	.db   7,252,  7,240, 15,252,  3,248
	.db  31,252,  3,252, 63,222,  3,252
	.db  63, 14,  3,252, 63, 14,  7,254
	.db 127, 14,  7,254,126, 14,  4, 62
	.db 126, 15, 12, 62,127, 15, 28, 62
	.db 255,142, 60, 62,255,134, 28, 62
	.db 127,132, 28,126,127,132, 25,254
	.db  63,  0, 17,254, 30,  0,  1,254
	.db  30,  0,  0,254, 14,  0,  0,255
	.db  15,  0,  0,255,  7,  0,  0,255
	.db   2,  0,  0,254,  0,  0,  1,192
	.db   0,  0,  1,128

	.if	0	;.comment otherbmp
	; ThreeHeads black
	.db 0,0,112,0,0,1,252,0
	.db 0,3,254,0,0,7,255,0
	.db 0,15,255,0,0,15,255,128
	.db 0,15,255,128,2,7,255,128
	.db 15,135,255,128,31,195,255,128
	.db 31,193,255,0,63,199,255,0
	.db 63,131,252,8,63,131,254,60
	.db 127,131,254,126,127,129,252,254
	.db 63,128,248,254,15,129,240,255
	.db 15,195,224,255,7,199,224,254
	.db 7,199,240,124,7,239,240,248
	.db 15,239,241,240,31,239,243,224
	.db 63,239,243,192,63,255,247,192
	.db 63,255,255,224,127,255,255,224
	.db 127,255,255,240
	.endif		;.comment otherbmp

fontmem = buffer43 + 0x78	; 0x4378
vidmem = buffer43 + 0xb0	; 0x43b0

end_3:				; falls through to part 4

;------------------------------------------------------------------------------
;
; As yet untitled
; The Calodox 1k ZX81 Intro
; Copyright (c) 2003 Sebastian Gerlach
;
; 4. Octaedron
;
; Displays rotating 3D octaedrons. Yeah!
;
;------------------------------------------------------------------------------

	ld	hl,#begin_4
	ld	de,#end_4 - begin_4 + 1
	call	mock_load

	ld hl,#fpoint
	ld de,#buffer42
	ld bc,#32
	ldir

begin_4:

hoscoff = 174+3

;rmat:
rmat	=	buffer40 + 0x34
;	ld sp, 0x42fe
	ld ix, #traceproc_4

	out (0xfe), a

; Transposed rotation matrix
; This is executed once on startup, but is just a bunch of nops...
; And we overwrite the first 9 bytes of initialization code as well
	.db 0
	.db 0,0

loop_around_4:
	ld hl, (frames_4)
	inc hl
	ld (frames_4), hl

	ld a, h			; High part of frame counter
	ld h, #buffer40_highbyte	; 0x40		; High part of all mod addresses

	cp #6
	jr c, nodie

	jp end_4		; was jr

nodie:
	cp #5
	jr c, nodecr
	ld a, l
	cpl
	rrca
	rrca
	rrca
	and #31
	inc a
	ld (modld+1), a
	jr norot

nodecr:
	cp #3
	jr c, noosc
	ld hl, #hoscdelta+1	; ld l,
	ld (hl), #1
	ld a, (frames_4)
	cp #192
	jr c, norot
	ld hl, #voscdelta+1	; ld l,
	ld (hl), #1
	jr norot
noosc:
	cp #2
	jr c, incren
	inc h
	ld hl, #rendercount+1	; ld l,
	ld (hl), #12
	dec h
	jr norot
incren:
	cp #1
	jr c, norot
	ld hl, #angadelta+1	; ld l,
	ld (hl), #2
	ld a, (frames_4)
	cp #165
	jr c, norot
	ld hl, #angbdelta+1	; ld l,
	ld (hl), #3
	jr norot
norot:

	ld hl, #hosc
	ld a, (hl)
hoscdelta:
	add #0
	ld (hl), a
	call sine_4
	sra a
	add #hoscoff
	inc hl			; inc l
	ld (hl), a
	inc hl			; inc l
	ld a, (hl)
voscdelta:
	add #0
	ld (hl), a
	call sine_4
	add #64
	inc hl			; inc l
	ld (hl), a

	; Create rotation matrix
	inc hl			; inc l
	ld a, (hl)
angadelta:
	add a,#0
	ld (hl), a
	ld b, a
	inc hl			; inc l
	ld a, (hl)
angbdelta:
	add a,#0
	ld (hl), a
	ld c, a

	ld a, b
	call cosine
	ld (rmat+3), a
	ld a,b
	call sine_4
	ld d, a			; d = sin a
	ld a,c
	call cosine
	ld (rmat+0), a
	call fixmul
	neg
	ld (rmat+5), a
	ld a,c
	call sine_4
	ld (rmat+4), a
	call fixmul
	ld (rmat+1), a
	xor a
	ld (rmat+2), a

	; Create transformed vertices
	ld iy, #rmat
	ld b, #6
nvert:
	ld a, 0(iy)
	neg
	ld 6(iy), a
	inc iy
	djnz nvert

	; Adjust coordinates
	ld b, #12
	ld hl, #rmat
nadj:
	ld a, (hl)
	add #64
	rra
	rrca
	and #0x1f
	ld (hl), a
	inc hl			; inc l
	djnz nadj

	ld c, #1
	ld iy, #edges
plotb:
	; Wait for retrace
	ld hl, #lflag_4
	xor a
	ld (hl), a
waittrace:
	or (hl)
	jr z, waittrace

	; Render vertices
	call clear

rendercount:
	ld b, #4
nedge:
	push bc
	call getlc
	ex de,hl
	call getlc

	call bresenham
	pop bc
	djnz nedge

	dec c
	jr nz, plotb

	jp loop_around_4

hosc:	.db 0
hoscs:	.db 32+hoscoff
vosc:	.db 0
voscs:	.db 64
anga:	.db 0
angb:	.db 0

frames_4:	.dw 0h

edges:
	.db 0+rmat-buffer40,2+rmat-buffer40	; 	.db 0+rmat-0x4000,2+rmat-0x4000
	.db 2+rmat-buffer40,6+rmat-buffer40	; 	.db 2+rmat-0x4000,6+rmat-0x4000
	.db 6+rmat-buffer40,8+rmat-buffer40	; 	.db 6+rmat-0x4000,8+rmat-0x4000
	.db 8+rmat-buffer40,0+rmat-buffer40	; 	.db 8+rmat-0x4000,0+rmat-0x4000
	.db 0+rmat-buffer40,4+rmat-buffer40	; 	.db 0+rmat-0x4000,4+rmat-0x4000
	.db 4+rmat-buffer40,6+rmat-buffer40	; 	.db 4+rmat-0x4000,6+rmat-0x4000
	.db 6+rmat-buffer40,10+rmat-buffer40	; 	.db 6+rmat-0x4000,10+rmat-0x4000
	.db 0+rmat-buffer40,10+rmat-buffer40	; 	.db 0+rmat-0x4000,10+rmat-0x4000
	.db 2+rmat-buffer40,4+rmat-buffer40	; 	.db 2+rmat-0x4000,4+rmat-0x4000
	.db 4+rmat-buffer40,8+rmat-buffer40	; 	.db 4+rmat-0x4000,8+rmat-0x4000
	.db 8+rmat-buffer40,10+rmat-buffer40	; 	.db 8+rmat-0x4000,10+rmat-0x4000
	.db 2+rmat-buffer40,10+rmat-buffer40	; 	.db 2+rmat-0x4000,10+rmat-0x4000

;-------------------------------------------------
; getlc
; Load vertex coordinates into hl
; Vertex to load is pointed by (iy)
;-------------------------------------------------
getlc:
	ld a, (iy)		; Load vertex offset
	inc iy			; Increment vertex pointer
	ld (lin2+1), a		; Modify load line
lin2:
	ld hl, (rmat)		; Load into hl
	ret

;-------------------------------------------------
; drawproc
; Synchronous screen refresh
;-------------------------------------------------
drawproc_4:	ld a, (hoscs)
	call delay_4
	ld b, #14
hr_4:	djnz hr_4
	ld ix, #endofline_4
	ld a, #buffer43_highbyte	; 0x43
	ld i, a
	xor a
modld:	ld d, #32
	ld e, #32
nextline_4:	jp oneline_4+0x8000	; 10
oneline_4:	ld r,a			; 9
lflag_4:				; Place lflag here, it will not disturb anyone
	.db 0,0,0,0,0,0,0,0		; 64
	ld r,a				; 9
	.db 0,0,0,0,0,0,0,0		; 64
	ld r,a				; 9
	.db 0,0,0,0,0,0,0,0		; 64
	jp (ix)				; 8
endofline_4:				; = 155
	add a, #8
	ld b, #18 ;24
waithere:
	djnz waithere
	inc hl
	nop
	dec e
	dec d
	jr nz, nextline_4

	ld hl, #lflag_4
	inc (hl)			; Allow main loop to run

	xor a
	or e
	jr z, nowait
nextwait:
	ld a, #255
	call delay_4
	dec e
	jr nz,nextwait

nowait:
	ld a, (voscs)
	add #40+12+3

	ld ix, #traceproc_4
	jr doret_4

traceproc_4:
	in a, (0xfe)
	ld b, #80
stupid:
	djnz stupid

	ld ix, #drawproc_4
	out (0xff),a

	ld a, (voscs)
	neg
	add #128+52

doret_4:
	jp 0x029e

;-------------------------------------------------
; fixmul
; Multiply b by c, fixed point 2.6
; In:	d - First value
;	a - Second value
; Out:	a - Result
; Mod:
;-------------------------------------------------
;.comment mul

fixmul:
	push bc
	push de
	ld b, #7
	ld e, a
	bit 7, d
	jr z, ispos
	ld a, d
	neg
	set 7, a
	ld d, a
ispos:
	rlc d
	xor a
nbit:
	rlc d
	jr nc, zbit
	add e
zbit:
	sra e
	djnz nbit
	rlc d
	jr nc, positive
	neg
positive:
	pop de
	pop bc
	ret

;-------------------------------------------------
; bresenham accelerator table
;-------------------------------------------------
;	.ds 0x4200-.
fpoint:
	B0 = 0xc6+0x38
	B1 = 0xc6+0x28
	B2 = 0xc6+0x18
	B3 = 0xc6+0x08
	.db B0, B1, B2, B3
	.db B0, B1, B2, B3
	.db B0, B1, B2, B3
	.db B0, B1, B2, B3
	.db B0, B1, B2, B3
	.db B0, B1, B2, B3
	.db B0, B1, B2, B3
	.db B0, B1, B2, B3

;-------------------------------------------------
; clear
; Clears the screen
; Mod:	bc, de, hl
;-------------------------------------------------
clear:
	push bc
	ld hl, #buffer43	; 0x4300
	ld (hl), #0
	ld de, #buffer43 + 1	; 0x4301
	ld bc, #255
	ldir
	pop bc
	ret

;-------------------------------------------------
; bresenham
; Computes points along the line
; In:	de - Start xy coordinates
;	hl - End xy coordinates
; Mod:	a,hl,de,bc
;-------------------------------------------------
bresenham:
	ld bc, #0x141c		; inc d / inc e

	; Calculate dx
	ld a, h
	sub d
	jr nc, xpos
	neg
	inc b			; dec d
xpos:
	ld h, a

	; Calculate dy
	ld a, l
	sub e
	jr nc, ypos
	neg
	inc c			; dec e
ypos:
	ld l, a

	; Check dx<dy, flip otherwise
	cp h
	jr c,orderok
	ld a, h			; Exchange h and l (dx and dy)
	ld h, l
	ld l, a
	ld a, b			; Exchande b and c (inc/dec instructions)
	ld b, c
	ld c, a
orderok:
	ld a, b			; Modify code
	ld (bmod0), a
	ld a, c
	ld (bmod1), a

	ld a, h
	or l
	ret z
	ld a,h
	srl a
	scf

	ld b, h

	; h contains delta x
	; l contains delta y
	; a is the error term
	; b is the number of lines left
	; de is current position
npixel:
	bit 0,b
	jr z,noplot

	push af
	push hl
	ld h, #buffer42_highbyte	; 0x42
	ld l, d
	ld a,(hl)
	ld (modh+1),a
	ld a, e
	rlca
	rlca
	rlca
	srl l
	srl l
	add l
	ld l,a
	inc h
modh:
	set 0,(hl)
	pop hl
	pop af

noplot:
	sub a, l
bmod0:
	inc d			; Modified!
	dec b
	ret z
	jr nc, npixel
	add a, h
bmod1:
	inc e			; Modified!
	jr npixel

;-------------------------------------------------
; delay
; Delay for a+x clock cycles
;-------------------------------------------------
delay_4:
	ld b, a
	and #3
	ld hl, #insts_4
	add l
	ld l, a
	ld a, (hl)
	ld (strt_4), a
strt_4:
	nop

	srl b
	srl b
	ld a, b
	cpl
	and #3
	ld (jop_4-1), a
	jr jop_4
jop_4:
	nop
	nop
	nop
	srl b
	srl b
	ret z
	; Missing 6 cycles because ret not taken
loophere_4:
	dec b
	jr nz, loophere_4
	; Missing another 5 cycles because of last jr not taken
	ret z
	; Takes the 11 cycles we have left :-)
	; Simply ret would have been one cycle too fast for us here

insts_4:
	nop			; 4
	ret c			; 5
	inc hl			; 6
	ld a,(de)		; 7

;-------------------------------------------------
; cosine
; Return the cosine of the value in a
; In:	a - Value to take cosine of (from 0 to 255)
; Out:	a - Cosine of input (from 0 to 128)
; Mod:	None
;-------------------------------------------------
cosine:
	sub #64
;-------------------------------------------------
; sine
; Return the sine of the value in a
; In:	a - Value to take sine of (from 0 to 255)
; Out:	a - Sine of input (from 0 to 128)
; Mod:	None
;-------------------------------------------------
sine_4:
	push bc
	push hl
	ld hl, #sinetable
	ld c, a
	bit 6, c
	jr z, s_noflip_4
	cpl
s_noflip_4:
	and #0x3f
	srl a
	add l
	ld l, a
	ld	a,h
	adc	a,#0
	ld	h,a
	ld a, (hl)
	bit 7, c
	jr nz, s_done_4
	neg
s_done_4:
	pop hl
	pop bc
	ret

sinetable:
	.db  0, 3, 6, 9
	.db 12,15,18,21
	.db 24,27,30,32
	.db 35,38,40,42
	.db 45,47,49,51
	.db 52,54,56,57
	.db 58,59,60,61
	.db 62,62,63,63

end_4:				; falls through to part 5

;------------------------------------------------------------------------------
;
; As yet untitled
; The Calodox 1k ZX81 Intro
; Copyright (c) 2003 Sebastian Gerlach
;
; 5. Bitmap
;
; Displays a large overscanned Calodox logo
;
; ThreeHeads logo by Fred
;
;------------------------------------------------------------------------------

	ld	hl,#begin_5
	ld	de,#end_5 - begin_5 + 1
	call	mock_load

begin_5:

;	COUNT =  8	;BW:	unused

	ld ix, #traceproc_5
;	ld sp, 0x43fe
	out (0xfe), a

loop_around_5:

	ld b, #4
blub:
	ld hl, #lflag_5
	ld (hl), #0
tag_5:
	bit 0, (hl)
	jr z, tag_5

	push bc
	ld a, #0
	ld (buffer40), a	; 	ld (0x4000), a
	ld de, #buffer40 + 1	; 	ld de, #0x4001
	ld hl, #buffer40	; 	ld hl, #0x4000
	ld bc, #24
	ldir
	pop bc
	djnz blub

	ld a, (scrolloff)
	or a
	jr z, loop_around_5
	dec a
	ld (scrolloff), a

	jr loop_around_5

lflag_5:	.db 0

drawproc2:
	ld b, #16
	jr hr_5

drawproc_5:	ld b, #1
hr_5:	djnz hr_5
;	nop
	ld a, (scrolloff)
	cp a, #190
	jr c, yiek
	ld a, #190
	jp ziep
yiek:
	nop
	nop
	nop
ziep:	or a
	jr z, dok_5
	ld c, a
nline:	ld b, #14
wline:	djnz wline
	dec c
	ld r,a
	jp nz, nline
	jr strt_5
dok_5:	
	ld a,#0
	nop
strt_5:	exx
	ld hl, #bmpdata
	ld de, #buffer40	; 0x4000
	exx
	srl a
	neg
	ld b, #96
	add b
	ld b,a
	ld ix, #endofline_5
	ld a, #buffer40_highbyte	; 0x40
	ld i, a
	xor a

nextline_5:	exx
	jp oneline_5+0x8000			; 10
oneline_5:	ld r,a				; 9
	.db 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0	; 64  16x4
	.db 0,0,0,0,0,0,0,0			; 32   8x4
	jp (ix)					; 8
endofline_5:					; = 111
	ld b,(hl)				; 7
	ld c,#6					; 7
	inc hl					; 6
nextpos:
	ld e,(hl)				; 7
	inc hl					; 6
	ldi					; 16
	djnz nextpos				; 13

	ld b,c					; 7
zorg:
	ld a,#0
	ld r,a
	ld r,a
	nop
	djnz zorg				; 13

	exx
	nop
	djnz nextline_5				; 13
	ld b, #14
waiter_2:	djnz waiter_2
	inc hl
	ld b, #8
	ld a, #0x1e
	ld i,a
	ld ix, #endoftext
textlines:	jp textline+0x8000		; 10
textline:	.db 0x28,0x26,0x31,0x34,0x29,0x34,0x3d,0x00	; "CALODOX "
		.db 0x16,0x00,0x3c,0x2a,0x00,0x34,0x3c,0x33	; "- WE OWN"
		.db 0x00,0x3f,0x3d,0x24,0x1d,0,0,0		; " ZX81   "
	jp (ix)					; 8
endoftext:	ld c,#4
askd:	dec c
	jr nz, askd
	inc hl
	nop
	nop
	djnz textlines
	ld hl, #lflag_5
	ld (hl), #1		; Allow main loop to run
	ld ix, #traceproc_5
	jr doret_5

traceproc_5:
	in a, (0xfe)
	ld b, #80
here_5:	djnz here_5

	ld a, (interlace)
	xor #1
;	xor a
	ld (interlace), a

	jr z, altv
	ld ix, #drawproc_5
	jr fini
altv:
	ld ix, #drawproc2
fini:
	out (0xff),a
doret_5:
	ld a, #45
	jp 0x029e

interlace:	.db 0
scrolloff:	.db 255

bmpdata:
;-------------------------------------------------
; Big ThreeHeads by fred
;-------------------------------------------------

	; ThreeHeads
	.db 3,12,15,13,255,14,128
	.db 2,12,127,14,254
	.db 4,11,1,12,255,14,255,15,224
	.db 2,11,15,15,254
	.db 3,11,255,15,255,16,192
	.db 2,10,15,16,248
	.db 2,10,127,16,255
	.db 3,9,3,10,255,17,192
	.db 2,9,15,17,224
	.db 2,9,63,17,248
	.db 2,9,255,17,252
	.db 1,17,254
	.db 1,17,255
	.db 2,8,1,18,128
	.db 1,18,192
	.db 1,18,192
	.db 1,18,224
	.db 2,8,0,18,240
	.db 1,8,0
	.db 2,9,127,18,248
	.db 1,9,63
	.db 1,9,63
	.db 5,3,1,4,255,5,248,9,31,18,252
	.db 5,3,31,5,255,6,128,9,15,18,248
	.db 3,3,255,6,240,9,3
	.db 3,2,3,6,252,9,1
	.db 4,2,15,6,254,9,0,18,240
	.db 3,2,31,6,255,10,127
	.db 3,2,63,10,31,18,224
	.db 4,2,255,7,128,10,15,18,192
	.db 2,10,7,18,128
	.db 3,1,1,10,3,18,0
	.db 4,1,3,7,0,10,255,17,252
	.db 3,1,7,9,1,17,248
	.db 1,17,224
	.db 4,1,15,6,254,9,0,17,128
	.db 5,1,31,6,252,16,252,17,0,21,240
	.db 4,1,63,10,127,20,127,21,254
	.db 4,19,7,20,255,21,255,22,192
	.db 5,1,127,6,248,16,254,19,63,22,240
	.db 5,6,240,10,63,16,255,19,255,22,248
	.db 4,1,255,10,31,18,3,22,254
	.db 2,0,1,18,15
	.db 5,0,3,6,224,10,15,16,254,18,63
	.db 5,0,7,10,7,16,252,18,127,22,255
	.db 5,0,15,10,3,16,248,17,1,18,255
	.db 4,0,31,10,1,16,240,23,192
	.db 5,0,15,6,240,10,0,11,127,16,192
	.db 5,0,1,11,31,16,0,17,3,23,224
	.db 5,0,0,1,63,6,248,11,7,15,252
	.db 5,1,3,6,252,11,15,15,240,17,1
	.db 5,1,0,2,31,6,248,11,127,15,192
	.db 5,2,7,6,240,10,1,11,255,15,0
	.db 5,2,1,6,252,10,7,14,252,23,240
	.db 5,2,0,6,255,10,31,14,240,17,0
	.db 5,3,63,7,128,10,127,14,192,23,248
	.db 5,3,31,7,192,10,255,14,0,23,240
	.db 5,7,224,9,3,14,192,18,127,23,224
	.db 5,3,15,7,240,9,7,14,224,23,192
	.db 3,9,15,14,240,23,0
	.db 3,7,248,14,248,22,252
	.db 5,3,31,9,31,14,252,18,63,22,240
	.db 4,7,252,9,63,14,254,22,128
	.db 5,3,63,9,127,18,127,21,254,22,0
	.db 5,3,127,7,254,17,1,18,255,21,240
	.db 4,3,255,9,255,17,15,21,224
	.db 3,2,1,17,31,21,192
	.db 4,2,3,8,1,17,255,21,0
	.db 4,2,7,7,255,16,3,20,240
	.db 3,2,31,16,7,20,128
	.db 5,2,127,8,131,16,15,19,254,20,0
	.db 4,1,1,2,255,16,63,19,252
	.db 3,1,3,16,127,19,248
	.db 5,1,15,8,195,15,1,16,255,19,240
	.db 3,1,31,8,227,15,3
	.db 5,1,63,8,231,14,255,15,7,19,248
	.db 3,1,127,8,255,15,15
	.db 2,15,143,19,252
	.db 3,1,255,15,159,19,254
	.db 2,0,1,15,255
	.db 1,19,255
	.db 1,20,128
	.db 1,20,192
	.db 1,20,224
	.db 1,20,224
	.db 1,20,240
	.db 1,20,248
	.db 1,20,248
	.db 3,0,0,1,127,20,252
	.db 1,0,0
	.db 1,0,0
	.db 1,0,0
	.db 1,0,0
	.db 1,20,254
	.db 1,20,254

	.db 1,20,254

	.if	0	;.comment oldbmp
	; ThreeHeads, too
	.db 3,12,3,13,255,14,224
	.db 3,12,31,14,255,15,128
	.db 2,12,127,15,248
	.db 4,11,3,12,255,15,255,16,128
	.db 2,11,63,16,240
	.db 3,10,3,11,255,16,254
	.db 3,10,31,16,255,17,192
	.db 2,10,255,17,240
	.db 2,9,3,17,248
	.db 2,9,15,17,254
	.db 2,9,63,17,255
	.db 1,18,128
	.db 1,18,192
	.db 2,9,127,18,224
	.db 1,18,240
	.db 1,18,240
	.db 1,18,248
	.db 2,9,63,18,252
	.db 1,9,63
	.db 2,9,31,18,254
	.db 1,9,15
	.db 1,9,15
	.db 4,4,127,5,254,9,7,18,255
	.db 5,3,7,4,255,5,255,6,224,9,3
	.db 4,3,63,6,252,9,0,18,254
	.db 3,3,255,6,255,10,127
	.db 4,2,3,7,128,10,63,18,252
	.db 3,2,7,7,192,10,31
	.db 3,2,15,10,7,18,248
	.db 4,2,63,7,224,10,3,18,240
	.db 2,10,1,18,224
	.db 3,2,127,10,0,18,192
	.db 4,2,255,7,192,10,63,18,0
	.db 3,1,1,10,127,17,254
	.db 1,17,248
	.db 4,1,3,7,128,10,63,17,224
	.db 4,1,7,7,0,17,0,21,60
	.db 5,1,15,10,31,20,31,21,255,22,128
	.db 3,19,1,20,255,22,240
	.db 5,1,31,6,254,17,128,19,15,22,252
	.db 5,6,252,10,15,17,192,19,63,22,254
	.db 5,1,63,10,7,19,255,22,255,23,128
	.db 2,1,127,18,3
	.db 5,1,255,6,248,10,3,17,128,18,15
	.db 5,0,1,10,1,17,0,18,31,23,224
	.db 5,0,3,10,0,16,254,18,127,23,240
	.db 3,0,7,11,127,16,252
	.db 5,0,3,6,252,11,31,16,240,18,255
	.db 5,0,0,1,127,11,7,16,192,23,248
	.db 4,1,15,6,254,11,1,16,0
	.db 5,1,0,6,255,11,3,15,254,18,127
	.db 5,2,7,6,254,11,31,15,248,23,252
	.db 4,2,1,6,252,11,127,15,192
	.db 5,2,0,3,127,6,255,10,1,11,255
	.db 5,3,63,7,192,10,7,14,252,15,0
	.db 5,3,15,7,224,10,31,14,240,18,63
	.db 4,3,7,7,240,10,63,14,192
	.db 5,7,248,10,255,14,240,18,31,23,248
	.db 5,3,3,7,252,9,1,14,248,23,240
	.db 3,9,3,14,252,23,192
	.db 3,7,254,14,254,23,0
	.db 5,3,7,9,7,14,255,18,15,22,252
	.db 4,7,255,9,15,15,128,22,224
	.db 4,3,15,9,31,18,31,22,128
	.db 5,3,31,8,128,18,127,21,252,22,0
	.db 5,3,63,9,63,17,3,18,255,21,248
	.db 3,3,127,17,7,21,240
	.db 4,3,255,9,127,17,63,21,192
	.db 5,2,1,8,192,17,255,20,252,21,0
	.db 3,2,7,16,1,20,224
	.db 5,2,31,8,224,9,255,16,3,20,128
	.db 3,2,127,16,15,20,0
	.db 3,2,255,16,31,19,254
	.db 4,1,3,8,240,16,127,19,252
	.db 3,1,7,8,248,16,255
	.db 4,1,15,8,249,15,193,19,254
	.db 3,1,31,8,255,15,195
	.db 2,15,227,19,255
	.db 3,1,63,15,231,20,128
	.db 2,1,127,15,255
	.db 1,20,192
	.db 1,20,224
	.db 1,20,240
	.db 1,20,248
	.db 1,20,248
	.db 1,20,252
	.db 1,20,254
	.db 1,20,254
	.db 2,1,31,20,255
	.db 1,1,31
	.db 1,1,31
	.db 1,1,31
	.db 1,1,31
	.db 1,21,128
	.db 1,21,128

	.db 1,21,128
	.endif		;.comment oldbmp

end_5:

;------------------------------------------------------------------------------

	; hl: starting address
	; de: length
mock_load:
	out	(0xfd),a
	ld	a,#5
	ld	bc,#0
ml_wait:
	push	af
	call	mock_wait
	pop	af
	dec	a
	jr	nz,ml_wait
ml_byte:
	call	mock_wait

	ld	a,(hl)
	inc	hl
	ld	c,#8
ml_bit:
	push	af

	rla
	sbc	a,a
	and	#16
	add	a,#8
	ld	b,a

	in	a,(0xfe)
	djnz	.
	out	(0xff),a

	pop	af
	dec	c
	jr	nz,ml_bit

	ld	bc,#10
	dec	de
	ld	a,d
	or	a,e
	jr	nz,ml_byte

	ld hl,#buffer
	ld de,#buffer+1
	ld bc,#BUFFER_SIZE-1
	ld (hl),#0
	ldir

	ret

mock_wait:
	in	a,(0xfe)
	out	(0xff),a
	dec	bc
	ld	a,b
	or	a,c
	jr	nz,mock_wait

	ret

;- some memory needed for every part ----------------------------

	; we'll overwrite BASIC stuff, but who cares?

BUFFER_SIZE	=0x300

buffer		=	(. + 0xff) & 0xff00	; a relocation error appears but it doesn't harm
buffer_highbyte	=	buffer >> 8

buffer40		= buffer + 0x0000
buffer40_highbyte	= buffer_highbyte + 0
buffer42		= buffer + 0x0100
buffer42_highbyte	= buffer_highbyte + 1
buffer43		= buffer + 0x0200
buffer43_highbyte	= buffer_highbyte + 2

	.db	0x76		; N/L of first line

;- The second line contains the call to the machine code --------

line2:
	.db	0,2
	.dw	dsp-.-2
	.db	0xF9		; RAND
	.db	0xD4		; USR
	.db	0xC5		; VAL
	.db	0x0b		; "
	.db	0x1d		; 1
	.db	0x22		; 6
	.db	0x21		; 5
	.db	0x1d		; 1
	.db	0x20		; 4
	.db	0x0b		; "
	.db	0x76		; N/L

dsp:
	.db	0x76		; N/L
	.db	0x76,0x76,0x76,0x76,0x76,0x76,0x76,0x76
	.db	0x76,0x76,0x76,0x76,0x76,0x76,0x76,0x76
	.db	0x76,0x76,0x76,0x76,0x76,0x76,0x76,0x76

var:
	.db	0x80
last:

;= The end ======================================================
